package machinelearning;

/**
 *
 * @author  Anat Nesichi & Moshe Goren
 */
import java.util.*;

/**
 * Stores a map of words and their frequencies
 * @author Anat Nesichi & Moshe Goren
 */
public class WordMap
{

    /**
     * Simple wrapper for 'int' - allows updating value
     */
    private class Counter
    {

        public int count = 0;

        public Counter(int value)
        {
            count = value;
        }

        @Override
        public String toString()
        {
            return Integer.toString(count);
        }
    }
    
    // Maps words to counters
    private HashMap<String, Counter> map;   

    /**
     * Passing the expected maximum of words helps with performance
     * @param expectedSize
     */
    public WordMap(int expectedSize)
    {
        map = new HashMap<String, Counter>(expectedSize);
    }

    /**
     * Creates an empty map when expected size is unknown
     */
    public WordMap()
    {
        map = new HashMap<String, Counter>();
    }
    

    /**
     * Add a single word to the WordMap
     * @param word
     * <p>
     * If word already exists in map, it's frequency counter is increased by one.
     */
    public void Add(String word)
    {
        if (!map.containsKey(word))
        {
            map.put(word, new Counter(1));
        }
        else
        {
            Counter freq = map.get(word);
            freq.count++;
        }
    }

    /**
     * Add a set of words to map.
     * @param words
     * <p>
     * This method is used for creating the dictionaries from the word sets of
     * several documents. The frequency then relates to the number of documents
     * that contain the word
     */
    public void Add(Set<String> words)
    {
        Iterator<String> wordsIt = words.iterator();

        while (wordsIt.hasNext())
        {
            this.Add(wordsIt.next());
        }
    }

    /**
     *
     * @param word
     * @return 'true' if document has word
     */
    public boolean hasWord(String word)
    {
        return map.containsKey(word);
    }

    /**
     *
     * @return Unordered set of words contained in document
     */
    public Set<String> getWordsSet()
    {
        return map.keySet();
    }

    /**
     *
     * @return The number of words contained in document (<b>not</b> including all repetitions)
     */
    public int getWordCount()
    {
        return map.size();
    }

    /**
     *
     * @param word
     * @return The frequency of the requested word
     */
    public int WordFreq(String word)
    {
        Counter freq = map.get(word);
        int ret = 0;
        if (freq != null)
        {
            ret = freq.count;
        }

        return ret;
    }
}
